<template>
  <div class="p-4.5 md:h-full flex flex-col">
    <SearchForm
      v-model:columns="columns"
      :title="authOnly ? t('routes.auth') : t('aiot.user.list')"
      :select-data="selectData"
      :keyword-search-data="keywordSearchData"
      :required-keys="requiredKeys"
      :add-btn-text="t('aiot.user.add')"
      :add-btn-permission-code="PermissionCode.USER_CREATE"
      :show-add-btn="!authOnly"
      :del-btn-text="t('aiot.user.delUser')"
      :del-btn-props="authOnly ? void 0 : { onClick: delUsers, disabled: selectedRowKeys.length === 0 }"
      :del-btn-permission-code="PermissionCode.USER_DELETE"
      :del-btn-disabled-mes="delBtnDisabledMes"
      @add="showCreateModal"
      @search="onSearch"
    />
    <div class="flex-1 md:overflow-hidden rounded-px-1">
      <SlTable
        :columns="columns"
        row-key="userId"
        :data-source="tableData"
        :pagination="pagination"
        :loading="tableLoading"
        :row-selection="
          authOnly
            ? null
            : {
                type: 'checkbox',
                selectedRowKeys,
                onChange,
              }
        "
        :search-model="searchModel"
      >
        <template #bodyCell="{ column, record }: BodyCellOptions<UserItem>">
          <a-space v-if="column.dataIndex === 'oper'">
            <!-- <a class="inline-block whitespace-nowrap" @click="showSetAuth(record)">{{ t("aiot.user.setAuth") }}</a> -->
            <a-button type="link" @click="showSetAuth(record)">
              {{ t("aiot.user.checkAuth") }}
            </a-button>
            <DropdownOper v-if="!authOnly" v-model:visible="record.operVisible" :record="record" :data="operData">
            </DropdownOper>
          </a-space>
          <div v-else-if="column.dataIndex === 'isLocked'">
            <a-tag class="sl-tag !mr-2 !mb-2" :color="record.isActivated ? 'green' : 'red'">
              {{ record.isActivated ? t("aiot.user.active") : t("aiot.user.unActive") }}
            </a-tag>
            <a-tag class="sl-tag" :color="record.isLocked ? 'red' : 'green'">
              {{ record.isLocked ? t("common.stopUse") : t("common.enable") }}
            </a-tag>
          </div>
          <a v-else-if="column.dataIndex === 'nickName'" href="javascript:void(0)" @click="showCheckModal(record)">
            <EllipsisText :max-len="10" :text="record.nickName" />
          </a>
        </template>
      </SlTable>
    </div>
    <CreateUserModal
      v-model:visible="createVisible"
      :columns="columns"
      :get-org-data="getOrgData"
      :is-platform="!!isPlatform"
      @create="afterCreate"
    />
    <CURDDialog
      ref="curdDialogForm"
      :model="userModel"
      :table-data="tableData"
      :update-title="t('aiot.user.editUserInfo')"
      :check-title="t('aiot.user.userDetail')"
      :delete-message="t('aiot.user.delUserMes')"
      :show-options="showOptions"
      :columns="columns"
      :model-form-setting="userModelFormSetting"
      :oper-data="operData"
      :curd="curd"
      id-key="userId"
      :reload-table="reloadTable"
      :z-index="1001"
      @open="userModalOpen"
    >
    </CURDDialog>
    <InsideDrawer
      v-model:visible="funcAuthDrawerVisible"
      :w-class="canAuthUpdate ? 'md:!w-252' : void 0"
      :title="
        (canAuthUpdate ? t('aiot.role.editFuncAuth') : t('aiot.role.checkAuth')) +
        (curSetAuthRecord ? `(${curSetAuthRecord.nickName})` : '')
      "
      :z-index="1001"
      :hide-ok-btn="!canAuthUpdate"
      @ok="updateFuncAuth"
    >
      <SelectApps v-if="!isPlatform" v-model:value="curUserApps" class="mb-4.5" :disabled="true"></SelectApps>
      <AuthList
        v-model:value="authValueToUpdate"
        :is-update="false"
        :server-value="curUserPermissions"
        :is-admin="isAdmin"
      />
    </InsideDrawer>
    <UserDetailModal
      v-model:visible="detailVisible"
      :record="detailCurRecord"
      @update-info="showUpdateModalFromDetail"
      @update-func-auth="funcAuthDrawerVisible = true"
    />
    <LocationDialog v-model:visible="locDgVisible" @ok="chooseLoc" />
  </div>
</template>
<script lang="ts" setup>
import { computed, onMounted, reactive, Ref, ref } from "vue";
import { useI18n } from "/@/locales/useI18n";
import { Api as userApi, authorizedUserFunctions, lockUserByUserId } from "/@/api/aiot/user";
import type { UserItem, UserSearchModel } from "/@/api/aiot/user/models";
import { useCURD } from "/@/hooks/useCURD";
import {
  CURDAction,
  CURDDialogExpose,
  CURDModalEvent,
  OperItem,
  ShowCURDModalOptions,
} from "/@/components/CURDDialog/models";
import type { OrganizationItem } from "/@/api/aiot/organization/models";
import UserDetailModal from "./UserDetailModal.vue";
import { OrderRule } from "/@/api/models";
import type { KeywordSearchItem, SelectItem } from "/@/types/components";
import type { AuthorizedRoleFunctionsParams, RoleFunctionMenuItem } from "/@/api/aiot/role/models";
import { getFunctionsByUserId, getRoleById } from "/@/api/aiot/role";
import { message } from "ant-design-vue";
import type { TableProps, TableColumnProps } from "ant-design-vue";
import { useUserModel } from "./useUserModel";
import InfoModal from "/@/components/InfoModal";
import type { BodyCellOptions } from "/@/types/antd";
import { OperPermissionType } from "/@/api/aiot/role/models";
import { AiotSubApp, getAiotSubAppData } from "/@/base/data";
import { useUserStore } from "/@/stores/aiot/user";
import { PermissionCode } from "/@/api/permissionCode";
// import { useUserStore } from "/@/stores/aiot/user";

const props = defineProps<{
  authOnly?: boolean;
  isPlatform?: boolean;
}>();
const { t } = useI18n();
const userStore = useUserStore();
/**
 * model
 */
const { userModel, userModelFormSetting, getOrgData, locDgVisible, chooseLoc, curdDialogForm } = useUserModel({
  isPlatform: props.isPlatform,
  hasRole: true,
  getPopupContainer() {
    // if (editUserDialogIns.value) {
    //   const el = editUserDialogIns.value.getFormContainer();
    //   if (el) {
    //     return el;
    //   }
    // }
    return document.body;
  },
});
/**
 * table
 */
const columns = ref<TableColumnProps<UserItem>[]>([
  {
    title: t("common.personName"),
    dataIndex: "nickName",
    fixed: "left",
    ellipsis: true,
    width: 100,
  },
  {
    title: "手机号",
    dataIndex: "phone",
    width: 100,
  },
  {
    title: "用户角色",
    dataIndex: "roles",
    width: 100,
  },
  {
    title: t("common.status"),
    dataIndex: "isLocked",
    width: 100,
  },
  {
    title: t("aiot.user.depart"),
    dataIndex: "organizations",
    width: 100,
  },
  {
    title: "岗位",
    dataIndex: "positionName",
    width: 100,
  },
  {
    title: t("aiot.user.email"),
    dataIndex: "companyEmail",
    width: 60,
  },
  // {
  //   title: t("common.createTime"),
  //   dataIndex: "createdOn",
  //   width: 100,
  // },
  {
    title: t("common.oper"),
    dataIndex: "oper",
    fixed: "right",
    width: 100,
  },
]);
let defaultAccountUserId = "";
const delBtnDisabledMes = computed(() => {
  if (selectedRowKeys.value.length === 0) {
    return t("aiot.userGroupManage.plzSel");
  }
  if (selectedRowKeys.value.includes(defaultAccountUserId)) {
    return t("aiot.user.defaultCannotDelBatch");
  }
  return "";
});
const selectedRowKeys = ref<string[]>([]);
function onChange(keys) {
  selectedRowKeys.value = keys;
}
function delUsers() {
  showOptions.value = { action: CURDAction.DELETE, ids: selectedRowKeys.value, message: t("aiot.user.delSelUser") };
}

const { pagination, tableData, curd, tableLoading, reloadTable, searchModel } = useCURD<UserItem, UserSearchModel>({
  getPageUrl: userApi.usersPage,
  updateUrl: userApi.updateUser,
  deleteUrl: userApi.removeUser,
  loadOnMounted: false,
  onLoadSuccess(data) {
    selectedRowKeys.value = [];
    defaultAccountUserId = "";
    for (let i = 0; i < data.length; i++) {
      if (data[i].isSystem) {
        defaultAccountUserId = data[i].userId as string;
        break;
      }
    }
    if (detailVisible.value) {
      const target = data.find((el) => el.userId === detailCurRecord.value?.userId);
      if (target) {
        detailCurRecord.value = target;
      }
    }
    // showOptions.value = void 0;
  },
});
function userModalOpen({ action, record, formItemData }: CURDModalEvent<UserItem>) {
  const el = formItemData.find((el) => el.key === "roleId");
  if (el && el.props && record) {
    el.props.disabled = action === CURDAction.UPDATE && !!record.isSystem;
  }
}
let _operData: OperItem<UserItem>[] = props.authOnly
  ? []
  : [
      {
        label: t("common.checkDetail"),
        handler: showDetailModal,
        showInDialog: false,
      },
      {
        label: t("common.edit"),
        // operType: OperPermissionType.MANAGE,
        permissionCode: PermissionCode.USER_UPDATE,
        handler: showUpdateModal,
      },
      {
        label: (record) => (record.isLocked ? t("common.enable") : t("common.stopUse")),
        permissionCode: PermissionCode.USER_LOCK,
        // operType: OperPermissionType.MANAGE,
        disabledMes: (record) => (record.isSystem ? t("aiot.user.defaultCannotForbid") : ""),
        danger: (record) => !record.isLocked,
        async handler(record: UserItem, isCURDDialog) {
          InfoModal.warningConfirm({
            content: record.isLocked
              ? t("aiot.user.enableUserMes", { account: record.nickName })
              : t("aiot.user.disableUserMes", { account: record.nickName }),
            async onOk() {
              if (!curd || !curd.update) return;
              const result = await lockUserByUserId({
                userId: record.userId as string,
                lock: record.isLocked ? 0 : 1,
              });
              if (result) {
                message.success(t("common.operSuccess"));
                await reloadTable();
                if (isCURDDialog) {
                  //更新传进去的记录数据
                  const index = tableData.value.findIndex((el) => el.userId === record.userId);
                  if (index >= 0) {
                    showOptions.value = { action: CURDAction.CHECK, record: tableData.value[index] };
                  }
                }
              }
            },
          });
        },
      },
      {
        label: t("common.delete"),
        type: "primary",
        permissionCode: PermissionCode.USER_DELETE,
        disabledMes: (record) => (record.isSystem ? t("aiot.user.defaultCannotDel") : ""),
        danger: true,
        handler: (record) => {
          showOptions.value = { action: CURDAction.DELETE, record };
        },
      },
    ];
if (props.isPlatform && _operData.length > 0) {
  _operData.splice(0, 1);
}
const operData = ref<OperItem<UserItem>[]>(_operData);
/**
 * func auth
 */
let curSetAuthRecord = ref<UserItem>();
const funcAuthDrawerVisible = ref(false);
const authValueToUpdate = ref<AuthorizedRoleFunctionsParams>();
const curUserPermissions = ref<RoleFunctionMenuItem[]>([]);
const curUserApps = ref<AiotSubApp[]>([]);
const canAuthUpdate = ref(false);
const isAdmin = ref(false);
//更新用户权限
async function updateFuncAuth() {
  if (!curSetAuthRecord.value) return;
  const re = await authorizedUserFunctions({
    userId: curSetAuthRecord.value.userId,
    userFolderPermissions: authValueToUpdate.value?.roleFolderPermissions,
    userMenuPermissions: authValueToUpdate.value?.roleMenuPermissions,
  });
  if (re) {
    funcAuthDrawerVisible.value = false;
    message.success(t("common.operSuccess"));
    if (detailVisible.value) {
      refreshAuth();
    }
  }
}
async function refreshAuth() {
  if (!curSetAuthRecord.value) return;
  if (curSetAuthRecord.value.roleId) {
    isAdmin.value = userStore.isAdminType(curSetAuthRecord.value.roleTypes);
    if (isAdmin.value) {
      curUserApps.value = getAiotSubAppData().map((el) => el.value);
      return;
    }
    const roleItem = await getRoleById(curSetAuthRecord.value.roleId as string);
    if (roleItem) {
      curUserApps.value = roleItem.applicationPermissions || [];
      if (roleItem.rolePermissions) {
        const value = JSON.parse(roleItem.rolePermissions) as RoleFunctionMenuItem[];
        curUserPermissions.value = value;
        return;
      }
    }
  }
  curUserApps.value = [];
  curUserPermissions.value = [];
}
async function showSetAuth(record: UserItem) {
  curSetAuthRecord.value = record;
  //先获取权限
  await refreshAuth();
  funcAuthDrawerVisible.value = true;
}
/**
 * searchForm
 */
const selectData = ref<SelectItem[]>([
  {
    label: t("common.department"),
    value: "",
    key: "organizationId",
    isTreeSelect: true,
    containerWidth: 260,
    props: {
      treeData: [],
      loading: true,
      fieldNames: { label: "companyShortName", value: "companyId" },
      treeNodeFilterProp: "companyShortName",
      treeNodeLabelProp: "companyShortName",
      virtual: false,
    },
  },
  {
    label: t("common.status"),
    value: "",
    key: "isLocked",
    options: [
      { value: "", label: t("common.all") },
      { value: 0, label: t("common.enable") },
      { value: 1, label: t("common.disable") },
    ],
  },
]);
if (props.isPlatform) {
  selectData.value.splice(0, 1);
}
onMounted(async () => {
  tableLoading.value = true;
  let companyId = "";
  if (!props.isPlatform) {
    const data = await getOrgData();
    const selectProps = selectData.value[0].props;
    if (selectProps) {
      let compData: OrganizationItem[] = []; //[{ companyId: "", companyShortName: t("common.all") }];
      selectProps.loading = false;
      selectProps.treeData = compData.concat(data);
      if (data.length > 0) {
        selectData.value[0].value = companyId = data[0].companyId as string;
      }
    }
  }
  reloadTable({
    model: {
      organizationId: companyId,
    },
    sort: "CreatedOn",
    order: OrderRule.DESC,
  });
});
const keywordSearchData: KeywordSearchItem[] = [
  {
    key: "searchText",
    label: t("common.nameOrPhone"),
  },
];
async function onSearch(model) {
  await reloadTable({ model });
}
const requiredKeys = ["nickName", "phone", "oper"];
/**
 * UpdateCheckModal
 */
function showCheckModal(record: UserItem) {
  showOptions.value = { action: CURDAction.CHECK, record };
}
function showUpdateModal(record: UserItem) {
  showOptions.value = { action: CURDAction.UPDATE, record };
}
function showUpdateModalFromDetail(record: UserItem) {
  showOptions.value = { action: CURDAction.UPDATE, record, hideNextPrev: true };
}
const showOptions = ref<ShowCURDModalOptions>();
/**
 * CreateModal
 */
const createVisible = ref(false);
function showCreateModal() {
  createVisible.value = true;
}
function afterCreate() {
  reloadTable();
}
/**
 * UserDetailModal
 */
const detailVisible = ref(false);
const detailCurRecord = ref<UserItem>();
function showDetailModal(record: UserItem) {
  curSetAuthRecord.value = record;
  detailCurRecord.value = record;
  detailVisible.value = true;
}
</script>
